import 'package:flutter/material.dart';
import 'package:xws/helpers/safe_state.dart';
import 'package:xws/models/goods/comment.dart';
import 'package:xws/models/goods/comment_obj.dart';
import 'package:xws/models/goods/goods_obj.dart';
import 'package:xws/models/goods/reply_obj.dart';
import 'package:xws/res/icons.dart';
import 'package:xws/utils/app_util.dart';
import 'package:xws/utils/dio_utils/request/goods_req.dart';
import 'package:xws/utils/theme_util.dart';
import 'package:xws/utils/tools_util.dart';
import 'package:xws/widgets/app_btn.dart';
import 'package:xws/widgets/app_text_field.dart';
import 'package:xws/widgets/safe_appbar.dart';
import 'package:xws/widgets/sticky_delegate.dart';

import 'comment_item.dart';

/// 评论区
class CommentBox extends StatefulWidget {
  const CommentBox({
    Key? key,
    required this.goodsObj,
    this.refresh,
  }) : super(key: key);

  @override
  _CommentBoxState createState() => _CommentBoxState();

  final GoodsObj goodsObj;

  final Function()? refresh;
}

class _CommentBoxState extends State<CommentBox> with SafeState<CommentBox> {
  GoodsObj get _g => widget.goodsObj;

  /// 回复对象
  Comments? _replyComments;

  /// 焦点
  late FocusNode _focusNode;
  late TextEditingController _controller;

  @override
  void initState() {
    super.initState();
    _focusNode = FocusNode();
    _controller = TextEditingController();
  }

  @override
  void dispose() {
    _focusNode.dispose();
    super.dispose();
  }

  /// 评论/回复
  Future<void> _tapToReply({CommentObj? c}) async {
    if (c == null && _replyComments != null) {
      safeSetState(() => _replyComments = null);
      _focusNode.unfocus();
    }

    if (c != null) {
      _focusNode.requestFocus();
      safeSetState(() => _replyComments = c);
    }
  }

  /// 发送评论
  Future<void> _submit() async {
    if (_controller.text.trim().isEmpty) {
      ct('内容为空');
      return;
    }

    loading(context);

    if (_replyComments == null) {
      /// 回复物主 (留言)
      final CommentObj? r = await commentGoods<CommentObj>(
        goodsId: _g.id,
        content: _controller.text,
      );

      if (r != null) {
        safeSetState(
          () {
            r.replyList = <ReplyObj>[];
            _g.commentCount++;
            _g.commentList.add(r);
          },
        );

        _controller.clear();

        widget.refresh?.call();
      }
    } else {
      /// 回复楼主
      final ReplyObj? r = await commentGoods<ReplyObj>(
        goodsId: _g.id,
        content: _controller.text,
        commentId: _replyComments?.id,
      );

      if (r != null) {
        safeSetState(
          () {
            _g.commentCount++;
            final int index = _g.commentList.indexWhere(
              (CommentObj cobj) => cobj.id == _replyComments?.id,
            );

            if (index < 0) {
              ct('评论不存在');
              close(context);
              return;
            }

            _g.commentList[index].replyList.add(r);

            _replyComments = null;
          },
        );

        _controller.clear();

        widget.refresh?.call();
      }
    }

    close(context);
  }

  @override
  Widget build(BuildContext context) {
    return GestureDetector(
      onTap: () => pop(context),
      child: Material(
        color: Colors.transparent,
        child: Stack(
          alignment: Alignment.bottomCenter,
          children: <Widget>[_comment, _buildInputBox],
        ),
      ),
    );
  }

  /// 留言区
  Widget get _comment {
    return DraggableScrollableActuator(
      child: GestureDetector(
        onTap: () {
          _tapToReply();
          hideKeyboard();
        },
        child: DraggableScrollableSheet(
          minChildSize: 0.6,
          initialChildSize: 0.6,
          maxChildSize: 0.9,
          builder: (BuildContext ctx, ScrollController c) {
            return Container(
              child: CustomScrollView(
                controller: c,
                slivers: <Widget>[_header, _buildCommentList],
              ),
              clipBehavior: Clip.antiAlias,
              decoration: BoxDecoration(
                color: white(context),
                borderRadius: const BorderRadius.vertical(top: Radius.circular(10)),
                boxShadow: <BoxShadow>[
                  BoxShadow(
                    blurRadius: 10,
                    color: Colors.black.withOpacity(0.1),
                  ),
                ],
              ),
            );
          },
        ),
      ),
    );
  }

  /// 头部
  Widget get _header {
    return SliverPersistentHeader(
      pinned: true,
      delegate: StickyDelegate(
        maxHeight: kToolbarHeight,
        child: SafeAppBar(
          autoBackIcon: false,
          withStatusBarHeight: false,
          titleText: '留言',
          titleTextStyle: TextStyle(
            fontSize: 18,
            fontWeight: FontWeight.bold,
            color: black(context).withOpacity(0.7),
          ),
          actions: <Widget>[_closeBtn],
        ),
      ),
    );
  }

  /// 关闭按钮
  Widget get _closeBtn {
    return AppBtn.noPadding(
      onTap: () => pop(context),
      color: Colors.transparent,
      width: 40,
      height: 40,
      radius: 0,
      alignment: Alignment.center,
      child: Container(
        child: Icon(
          Icons.close_rounded,
          color: black(context).withOpacity(0.4),
          size: 16,
        ),
        padding: const EdgeInsets.all(2),
        decoration: BoxDecoration(
          shape: BoxShape.circle,
          border: Border.all(
            color: black(context).withOpacity(0.4),
          ),
        ),
      ),
    );
  }

  /// 留言列表
  Widget get _buildCommentList {
    if (_g.commentCount == 0) {
      return SliverFillRemaining(
        child: Center(
          child: Column(
            mainAxisSize: MainAxisSize.min,
            children: <Widget>[
              Icon(
                IR.comment,
                size: 80,
                color: black(context).withOpacity(0.2),
              ),
              Text(
                '还没有人留言',
                style: TextStyle(
                  fontSize: 12,
                  color: black(context).withOpacity(0.5),
                ),
              ),
            ],
          ),
        ),
      );
    }
    return SliverPadding(
      padding: const EdgeInsets.symmetric(horizontal: 20).copyWith(
        bottom: 100,
        top: 10,
      ),
      sliver: SliverList(
        delegate: SliverChildBuilderDelegate(
          (_, int i) {
            final CommentObj commentObj = _g.commentList[i];
            return CommentItem(
              commentObj: commentObj,
              tapComment: () => _tapToReply(c: commentObj),
            );
          },
          childCount: _g.commentList.length,
        ),
      ),
    );
  }

  /// 输入框
  Widget get _buildInputBox {
    return AnimatedPadding(
      duration: const Duration(milliseconds: 200),
      curve: Curves.ease,
      padding: EdgeInsets.only(
        bottom: MediaQuery.of(context).viewInsets.bottom,
      ),
      child: Container(
        child: AppTextField(
          enabled: _g.status != GoodsStatus.DELIVERED,
          hintText: _hintText,
          maxLength: 50,
          controller: _controller,
          focusNode: _focusNode,
          fillColor: theme(context).withOpacity(0.05),
          contentPadding: const EdgeInsets.symmetric(
            horizontal: 20,
            vertical: 10,
          ),
          border: OutlineInputBorder(
            borderSide: BorderSide.none,
            borderRadius: BorderRadius.circular(30),
          ),
          suffixIcon: Padding(
            padding: const EdgeInsets.only(right: 4),
            child: AppBtn(
              onTap: _submit,
              text: '发送',
              radius: 20,
              padding: const EdgeInsets.symmetric(horizontal: 20, vertical: 6),
            ),
          ),
        ),
        color: white(context),
        padding: const EdgeInsets.all(20).copyWith(top: 10),
      ),
    );
  }

  String get _hintText => _g.status == GoodsStatus.DELIVERED
      ? '物品已送出'
      : _replyComments == null
          ? '给物主留言...'
          : '回复: ${_replyComments?.nickName}';
}
